package com.railway.switchs.action.business;

import com.railway.switchs.aspect.OperationLog;
import com.railway.switchs.base.BaseResponse;
import com.railway.switchs.constant.FileConstant;
import com.railway.switchs.constant.SystemConstant;
import com.railway.switchs.domain.dto.business.DeviceInfo;
import com.railway.switchs.domain.dto.business.RepairTask;
import com.railway.switchs.domain.dto.business.RoadSwitch;
import com.railway.switchs.domain.dto.business.SwitchInfo;
import com.railway.switchs.domain.dto.user.UserInfo;
import com.railway.switchs.domain.query.business.DeviceInfoQuery;
import com.railway.switchs.domain.query.business.RepairTaskQuery;
import com.railway.switchs.domain.query.business.RoadSwitchQuery;
import com.railway.switchs.domain.query.business.SwitchInfoQuery;
import com.railway.switchs.domain.query.user.UserInfoQuery;
import com.railway.switchs.domain.request.SendEmailRequest;
import com.railway.switchs.domain.response.FileUploadResponse;
import com.railway.switchs.enums.*;
import com.railway.switchs.service.business.IDeviceInfoService;
import com.railway.switchs.service.business.IRepairTaskService;
import com.railway.switchs.service.business.IRoadSwitchService;
import com.railway.switchs.service.business.ISwitchInfoService;
import com.railway.switchs.service.message.ISendEmailService;
import com.railway.switchs.service.user.IUserInfoService;
import com.railway.switchs.utils.DateUtil;
import com.railway.switchs.utils.StringUtil;
import com.railway.switchs.utils.UserUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Controller;
import org.springframework.validation.BindingResult;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.servlet.ModelAndView;
import org.ujmp.core.Matrix;
import org.ujmp.jmatio.ImportMatrixMAT;

import javax.servlet.http.HttpServletRequest;
import java.io.File;
import java.util.ArrayList;
import java.util.List;

/**
 * @ClassName RepairTaskAction
 * @Author 魏梓晟
 * @Version 1.0
 **/
@Controller
@Slf4j
@RequestMapping("/back/repairTask")
public class RepairTaskAction {

    @Autowired
    private IRepairTaskService repairTaskService;

    @Autowired
    private ISwitchInfoService switchInfoService;

    @Autowired
    private IRoadSwitchService roadSwitchService;

    @Autowired
    private IDeviceInfoService deviceInfoService;

    @Autowired
    private ISendEmailService sendEmailService;

    @Autowired
    private IUserInfoService userInfoService;

    @Value("${file.upload.path}")
    private String path ;

    /**
     * 进入检修任务列表（监管员）
     * @return
     */
    @RequestMapping(value = "/supervisorList",method = RequestMethod.GET)
    public String supervisorList(){
        return "repairTask/supervisorList";
    }

    /**
     * 进入检修任务列表（维修员）
     * @return
     */
    @RequestMapping(value = "/repairmanList",method = RequestMethod.GET)
    public String repairmanList(){
        return "repairTask/repairmanList";
    }

    /**
     * 进入检修任务列表（预警员）
     * @return
     */
    @RequestMapping(value = "/earnList",method = RequestMethod.GET)
    public String earnList(){
        return "repairTask/earnList";
    }

    /**
     *获取检修任务（监管员）
     * @param query
     * @return
     */
    @ResponseBody
    @RequestMapping(value = "/getSupervisorList",method = RequestMethod.POST)
    public RepairTaskQuery getSupervisorList(RepairTaskQuery query) {
        try {
            query.setSupervisorAccount(UserUtil.getUserAccount());
            query = repairTaskService.query(query);
            query.setCode(EnumReturnResult.RETURN_200.getCode());
        } catch (Exception e) {
            log.error("获取检修任务信息列表数据异常", e);
            query.setCode(EnumReturnResult.RETURN_404.getCode());
            query.setMsg("获取检修任务信息数据异常");
        }
        return query;
    }

    /**
     *获取检修任务（维修员）
     * @param query
     * @return
     */
    @ResponseBody
    @RequestMapping(value = "/getRepairmanList",method = RequestMethod.POST)
    public RepairTaskQuery getRepairmanList(RepairTaskQuery query) {
        try {
            query.setRepairmanAccount(UserUtil.getUserAccount());
            query = repairTaskService.query(query);
            query.setCode(EnumReturnResult.RETURN_200.getCode());
        } catch (Exception e) {
            log.error("获取检修任务信息列表数据异常", e);
            query.setCode(EnumReturnResult.RETURN_404.getCode());
            query.setMsg("获取检修任务信息数据异常");
        }
        return query;
    }

    /**
     *获取检修任务（预警员）
     * @param query
     * @return
     */
    @ResponseBody
    @RequestMapping(value = "/getEarnList",method = RequestMethod.POST)
    public RepairTaskQuery getEarnList(RepairTaskQuery query) {
        try {
            query = repairTaskService.query(query);
            query.setCode(EnumReturnResult.RETURN_200.getCode());
        } catch (Exception e) {
            log.error("获取检修任务信息列表数据异常", e);
            query.setCode(EnumReturnResult.RETURN_404.getCode());
            query.setMsg("获取检修任务信息数据异常");
        }
        return query;
    }

    /**
     * 进入新增页面
     * @return
     */
    @RequestMapping(value = "/add",method = RequestMethod.GET)
    public String preAdd(){
        return "repairTask/add";
    }

    /**
     * 发布检修任务
     * @param repairTask
     * @param result
     * @return
     */
    @ResponseBody
    @OperationLog(billType ="6",actionType ="0" )
    @RequestMapping(value = "/add",method = RequestMethod.POST)
    public BaseResponse add(@Validated RepairTask repairTask, BindingResult result) {
        BaseResponse response = new BaseResponse();
        try {
            if(result.hasErrors()){
                response.setCode(EnumReturnResult.RETURN_404.getCode());
                response.setMsg("RepairTask-add参数有误");
                log.info("RepairTask-add参数有误："+result.getAllErrors().toString());
                return response;
            }
            //根据道岔编号获取相关信息
            RoadSwitchQuery roadSwitchQuery = new RoadSwitchQuery();
            roadSwitchQuery.setSwitchCodeList(repairTask.getSwitchCode());
            List<RoadSwitch> roadSwitches = roadSwitchService.getList(roadSwitchQuery);
            if(StringUtil.isNotEmpty(roadSwitches)){
                repairTask.setRepairmanAccount(roadSwitches.get(0).getRepairmanAccount());
                repairTask.setSupervisorAccount(roadSwitches.get(0).getSupervisorAccount());
            }else{
                log.error("道岔未绑定铁路段道岔");
                response.setCode(EnumReturnResult.RETURN_404.getCode());
                response.setMsg("新增失败");
            }
            //时间转换
            repairTask.setCloseTime(DateUtil.StringToDate(repairTask.getCloseTimeStr(), EnumDateStyle.YYYY_MM_DD_HH_MM_SS));
            repairTask.setFinishTime(DateUtil.StringToDate(repairTask.getFinishTimeStr(), EnumDateStyle.YYYY_MM_DD_HH_MM_SS));
            //维修任务待处理
            repairTask.setTaskType(EnumRepairType.UNHANDLE.getCode());
            repairTaskService.add(repairTask);
            //修改道岔的状态为维修中
            SwitchInfo switchInfo = new SwitchInfo();
            switchInfo.setRunType(EnumRunType.MAINTENANCE.getCode());
            List<String> switchCodes = new ArrayList<>();
            switchCodes.add(repairTask.getSwitchCode());
            switchInfo.setSwitchCodeList(switchCodes);
            switchInfoService.editRunType(switchInfo);
            //维修部位待维修中
            if(EnumDeviceType.DEVICE_CONNECT.getCode().equals(repairTask.getRepairPlace())){
                //连接设备置为维修中
                DeviceInfo deviceInfo = new DeviceInfo();
                deviceInfo.setRunType(EnumRunType.MAINTENANCE.getCode());
                List<String> stringList = new ArrayList<>();
                stringList.add(switchInfo.getConnectCode());
                deviceInfo.setDeviceCodeList(stringList);
                deviceInfoService.editRunType(deviceInfo);
            }
            if(EnumDeviceType.DEVICE_CROSS.getCode().equals(repairTask.getRepairPlace())){
                //交叉设备置为维修中
                DeviceInfo deviceInfo = new DeviceInfo();
                deviceInfo.setRunType(EnumRunType.MAINTENANCE.getCode());
                List<String> stringList = new ArrayList<>();
                stringList.add(switchInfo.getCrossCode());
                deviceInfo.setDeviceCodeList(stringList);
                deviceInfoService.editRunType(deviceInfo);
            }
            if(EnumDeviceType.DEVICE_COMBINATION.getCode().equals(repairTask.getRepairPlace())){
                //组合设备置为维修中
                DeviceInfo deviceInfo = new DeviceInfo();
                deviceInfo.setRunType(EnumRunType.MAINTENANCE.getCode());
                List<String> stringList = new ArrayList<>();
                stringList.add(switchInfo.getCombinationCode());
                deviceInfo.setDeviceCodeList(stringList);
                deviceInfoService.editRunType(deviceInfo);
            }
            response.setCode(EnumReturnResult.RETURN_200.getCode());
            response.setMsg("新增成功");
        } catch (Exception e) {
            log.error("新增检修任务信息异常",e);
            response.setCode(EnumReturnResult.RETURN_404.getCode());
            response.setMsg("新增失败");
        }
        return response;
    }

    /**
     * 进入修改界面
     * @param id
     * @return
     */
    @RequestMapping(value = "/edit",method = RequestMethod.GET)
    public ModelAndView preEdit(Long id){
        ModelAndView mav = new ModelAndView();
        try{
            RepairTask repairTask = repairTaskService.get(id);
            mav.addObject("repairTask",repairTask);
            mav.setViewName("repairTask/edit");
        }catch (Exception e){
            log.error("获取铁路段道岔信息详情失败",e);
            mav.addObject(SystemConstant.ERROR_KEY,"系统异常");
            mav.setViewName("repairTask/supervisorList");
        }
        return mav;
    }

    /**
     * 修改检修任务
     * @param repairTask
     * @param result
     * @return
     */
    @ResponseBody
    @OperationLog(billType ="6",actionType ="1" )
    @RequestMapping(value = "/edit",method = RequestMethod.POST)
    public BaseResponse edit(@Validated RepairTask repairTask, BindingResult result) {
        BaseResponse response = new BaseResponse();
        try {
            if(result.hasErrors()){
                response.setCode(EnumReturnResult.RETURN_404.getCode());
                response.setMsg("RepairTask-edit参数有误");
                log.info("RepairTask-edit参数有误："+result.getAllErrors().toString());
                return response;
            }
            repairTaskService.edit(repairTask);
            response.setCode(EnumReturnResult.RETURN_200.getCode());
            response.setMsg("修改成功");
        } catch (Exception e) {
            log.error("修改检修任务信息异常",e);
            response.setCode(EnumReturnResult.RETURN_404.getCode());
            response.setMsg("修改失败");
        }
        return response;
    }

    /**
     * 删除检修任务
     * @param id
     * @return
     */
    @ResponseBody
    @OperationLog(billType ="6",actionType ="2" )
    @RequestMapping(value = "/delete",method = RequestMethod.POST)
    public BaseResponse delete(Long id) {
        BaseResponse response = new BaseResponse();
        try {
            repairTaskService.delete(id);
            response.setCode(EnumReturnResult.RETURN_200.getCode());
            response.setMsg("删除检修任务成功");
        } catch (Exception e) {
            log.error("删除检修任务异常",e);
            response.setCode(EnumReturnResult.RETURN_404.getCode());
            response.setMsg("删除检修任务失败");
        }
        return response;
    }

    /**
     * 提交审核检修任务
     * @param id
     * @return
     */
    @ResponseBody
    @OperationLog(billType ="6",actionType ="8" )
    @RequestMapping(value = "/uncheck",method = RequestMethod.POST)
    public BaseResponse uncheck(Long id) {
        BaseResponse response = new BaseResponse();
        try {
            RepairTask repairTask = repairTaskService.get(id);
            repairTask.setTaskType(EnumRepairType.UNCHECK.getCode());
            repairTaskService.edit(repairTask);
            response.setCode(EnumReturnResult.RETURN_200.getCode());
            response.setMsg("提交审核检修任务成功");
        } catch (Exception e) {
            log.error("提交审核检修任务异常",e);
            response.setCode(EnumReturnResult.RETURN_404.getCode());
            response.setMsg("提交审核检修任务失败");
        }
        return response;
    }

    /**
     * 审核检修任务不合格
     * @param id
     * @return
     */
    @ResponseBody
    @OperationLog(billType ="6",actionType ="9" )
    @RequestMapping(value = "/unQualified",method = RequestMethod.POST)
    public BaseResponse unQualified(Long id) {
        BaseResponse response = new BaseResponse();
        try {
            RepairTask repairTask = repairTaskService.get(id);
            repairTask.setTaskType(EnumRepairType.UNQUALIFIED.getCode());
            repairTaskService.edit(repairTask);
            response.setCode(EnumReturnResult.RETURN_200.getCode());
            response.setMsg("审核检修任务不合格成功");
        } catch (Exception e) {
            log.error("审核检修任务不合格异常",e);
            response.setCode(EnumReturnResult.RETURN_404.getCode());
            response.setMsg("审核检修任务不合格失败");
        }
        return response;
    }

    /**
     * 审核检修任务合格
     * @param id
     * @return
     */
    @ResponseBody
    @OperationLog(billType ="6",actionType ="A" )
    @RequestMapping(value = "/qualified",method = RequestMethod.POST)
    public BaseResponse qualified(Long id) {
        BaseResponse response = new BaseResponse();
        try {
            RepairTask repairTask = repairTaskService.get(id);
            repairTask.setTaskType(EnumRepairType.QUALIFIED.getCode());
            repairTaskService.edit(repairTask);
            response.setCode(EnumReturnResult.RETURN_200.getCode());
            response.setMsg("审核检修任务合格成功");
            //将道岔置为正常
            SwitchInfoQuery switchInfoQuery = new SwitchInfoQuery();
            switchInfoQuery.setSwitchCode(repairTask.getSwitchCode());
            SwitchInfo switchInfo = switchInfoService.getList(switchInfoQuery).get(0);
            switchInfo.setRunType(EnumRunType.USED.getCode());
            switchInfoService.edit(switchInfo);
            //将道岔的检修部位置为正常
            if(EnumDeviceType.DEVICE_CONNECT.getCode().equals(repairTask.getRepairPlace())){
                //连接设备置为正常
                DeviceInfo deviceInfo = new DeviceInfo();
                deviceInfo.setRunType(EnumRunType.USED.getCode());
                List<String> stringList = new ArrayList<>();
                stringList.add(switchInfo.getConnectCode());
                deviceInfo.setDeviceCodeList(stringList);
                deviceInfoService.editRunType(deviceInfo);
            }
            if(EnumDeviceType.DEVICE_CROSS.getCode().equals(repairTask.getRepairPlace())){
                //交叉设备置为正常
                DeviceInfo deviceInfo = new DeviceInfo();
                deviceInfo.setRunType(EnumRunType.USED.getCode());
                List<String> stringList = new ArrayList<>();
                stringList.add(switchInfo.getCrossCode());
                deviceInfo.setDeviceCodeList(stringList);
                deviceInfoService.editRunType(deviceInfo);
            }
            if(EnumDeviceType.DEVICE_COMBINATION.getCode().equals(repairTask.getRepairPlace())){
                //组合设备置为正常
                DeviceInfo deviceInfo = new DeviceInfo();
                deviceInfo.setRunType(EnumRunType.USED.getCode());
                List<String> stringList = new ArrayList<>();
                stringList.add(switchInfo.getCombinationCode());
                deviceInfo.setDeviceCodeList(stringList);
                deviceInfoService.editRunType(deviceInfo);
            }

        } catch (Exception e) {
            log.error("审核检修任务合格异常",e);
            response.setCode(EnumReturnResult.RETURN_404.getCode());
            response.setMsg("审核检修任务合格失败");
        }
        return response;
    }

    /**
     * 重新发布任务
     * @param id
     * @return
     */
    @ResponseBody
    @OperationLog(billType ="6",actionType ="5" )
    @RequestMapping(value = "/rePub",method = RequestMethod.POST)
    public BaseResponse rePub(Long id) {
        BaseResponse response = new BaseResponse();
        try {
            RepairTask repairTask = repairTaskService.get(id);
            repairTask.setTaskType(EnumRepairType.UNHANDLE.getCode());
            repairTaskService.edit(repairTask);
            response.setCode(EnumReturnResult.RETURN_200.getCode());
            response.setMsg("重新发布检修任务成功");
        } catch (Exception e) {
            log.error("重新发布检修任务异常",e);
            response.setCode(EnumReturnResult.RETURN_404.getCode());
            response.setMsg("重新发布检修任务失败");
        }
        return response;
    }

    /**
     * 提醒监管员
     * @param id
     * @return
     */
    @ResponseBody
    @RequestMapping(value = "/tips",method = RequestMethod.POST)
    public BaseResponse tips(Long id) {
        BaseResponse response = new BaseResponse();
        try {
            RepairTask repairTask = repairTaskService.get(id);
            UserInfoQuery query = new UserInfoQuery();
            query.setUserAccount(repairTask.getSupervisorAccount());
            List<UserInfo> userInfos = userInfoService.getList(query);
            if(StringUtil.isNotEmpty(userInfos)){
                String sendContent = "尊敬的用户：\n" +
                        "            您有一条检修任务需要重新发布,请及时处理！\n" +
                        "                                                                                                         铁路道岔故障检测信息管理部";
                SendEmailRequest sendEmailRequest = new SendEmailRequest();
                sendEmailRequest.setText(sendContent);
                sendEmailRequest.setHtmlText(false);
                sendEmailRequest.setTo(userInfos.get(0).getUserEmail());
                sendEmailRequest.setNickName(SystemConstant.REGITER_NICK_NAME);
                sendEmailRequest.setSubject("检测任务重新发布提醒");
                sendEmailService.sendEmail(sendEmailRequest);
                response.setCode(EnumReturnResult.RETURN_200.getCode());
                response.setMsg("提醒监管员重新发布检修任务成功");
            }else {
                log.error("发送邮件失败，原因：找不到监管员");
                response.setCode(EnumReturnResult.RETURN_404.getCode());
                response.setMsg("提醒监管员重新发布检修任务失败");
            }
        } catch (Exception e) {
            log.error("提醒监管员重新发布检修任务异常",e);
            response.setCode(EnumReturnResult.RETURN_404.getCode());
            response.setMsg("提醒监管员重新发布检修任务失败");
        }
        return response;
    }

    /**
     * 导入电压数据
     * @param file
     * @param request
     * @return
     * @throws Exception
     */
    @ResponseBody
    @RequestMapping("/import")
    public FileUploadResponse singleFileUpload(@RequestParam("file") MultipartFile file, HttpServletRequest request)throws Exception{
        FileUploadResponse response = new FileUploadResponse();
        try{
            //先将文件存储在本地
            file.transferTo(new File(path+file.getOriginalFilename()));
            //取电压数据
            File fileTemp = new File(path+file.getOriginalFilename());
            Matrix dataBase= ImportMatrixMAT.fromFile(fileTemp);
            int  col =(int)dataBase.getColumnCount();
            int  row = (int)dataBase.getRowCount();
            int rand=(int)(Math.random()*97) +3;
            List<Double> doubles = new ArrayList<>();
            List<Integer> ints = new ArrayList<>();
            for(int i = 0;i<row;i++){
                double asDouble = dataBase.transpose().getAsDouble(rand,i);
                doubles.add(asDouble);
                ints.add(i);
            }
            response.setIntData(ints);
            response.setDoublesData(doubles);
            response.setCode(FileConstant.FILE_UPLOAD_SUCCESS);
            response.setMsg("导入电压数据成功");
        }catch (Exception e){
            log.info("导入电压数据{}失败",file.getOriginalFilename());
            log.error("导入电压数据失败：",e);
            response.setCode(FileConstant.FILE_UPLOAD_ERROR);
            response.setMsg("导入电压数据异常");
        }
        return response;
    }
}
